import re
from time import sleep
import allure
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.support.wait import WebDriverWait 
from common.log import log


@allure.step("鼠标左键点击")
def object_left_click(driver, sel, timeout=10, retries: int = 1):
    """
    鼠标左键点击（支持自动重试）

    :param driver: WebDriver 实例
    :param sel: 元素定位元组，如 (By.XPATH, "//input[@id='user_name']")
    :param timeout: 每次等待元素可点击的超时时间
    :param retries: 失败后的重试次数，默认 1（即最多点击 2 次）
    :return: True 表示点击成功；若最终失败将抛出异常
    """

    last_exception = None
    for attempt in range(retries + 1):
        try:
            WebDriverWait(driver, timeout).until(EC.element_to_be_clickable(sel)).click()
            sleep(0.2)
            # 提取中文日志
            selen = re.sub('[^\u4e00-\u9fa5]+', '', str(sel))
            if selen:
                log.info(f"点击：{selen}")
            return True
        except Exception as e:
            last_exception = e
            if attempt < retries:
                log.warning(f"未定位到元素 {sel}（第 {attempt + 1} 次），重试中…")
                sleep(0.5)
                continue
            # 最后一次仍失败
            log.error(f"无法定位到该元素 {sel}，已重试 {retries + 1} 次后仍失败，异常：{e}")
            raise e  # 抛出异常交由调用方处理


@allure.step("元素可点击")
def object_clickable(driver, by, sel, timeout=20):
    try:
        WebDriverWait(driver, timeout).until(EC.element_to_be_clickable((by, sel)))
        return True
    except Exception as e:
        log.error(f"已经达到超时时间元素【{sel}】仍未加载出,不可点击，异常为，{e}")
        return e


@allure.step("元素可见")
def object_visible(driver, by, sel, timeout=20):
    try:
        WebDriverWait(driver, timeout).until(EC.visibility_of_element_located((by, sel)))
        return True
    except Exception as e:
        log.error(f"已经达到超时时间元素【{sel}】仍不可见,不可点击，异常为，{e}")
        return e


@allure.step("输入内容")
def object_send_keys(driver, sel, text, timeout=10):
    """
    输入内容
    :param timeout:
    :param driver:
    :param sel:
    :param text:
    :return:
    """
    try:
        WebDriverWait(driver, timeout).until(EC.element_to_be_clickable(sel)).clear()
        sleep(0.2)
        WebDriverWait(driver, timeout).until(EC.element_to_be_clickable(sel)).send_keys(text)
        sleep(0.2)
        selen = re.sub('[^\u4e00-\u9fa5]+', '', str(sel))
        if len(selen) > 0:
            log.info("点击: {},输入值：{}".format(selen, text))
        return True
    except Exception as e:
        log.error(f"无法定位到该元素，{sel}，异常为，\n{e}")
        return e


@allure.step("获取元素文本")
def object_get_text(driver, sel, timeout=10, mode=0):
    """
    获取sel元素文本
    :param mode:
    :param timeout:
    :param driver:
    :param sel:
    :return:
    """
    try:
        element = WebDriverWait(driver, timeout).until(EC.presence_of_element_located(sel))
        if mode == 0:
            log.info(element.text)
            return element.text
        elif mode == 1:
            log.info(element.get_attribute("textContent"))
            return element.get_attribute("textContent")
    except Exception as e:
        log.error(f"无法获取元素【{sel}】的文本，异常为，{e}")
        return None


